package de.hwr.sudokuspielehr.ui.component;

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.GridLayout;

import javax.swing.BorderFactory;
import javax.swing.JPanel;
import javax.swing.border.Border;

/**
 * 
 * @author J. Reischauer
 * 
 */
@SuppressWarnings("serial")
public class SudokuCellPanel extends JPanel {

	/**
	 * Default number.
	 */
	public static final int DEFAULT_NUMBER = -1;

	/**
	 * Backgound color of cell if its not changeable.
	 */
	private static final Color COLOR_CHANGEABLE = Color.WHITE;

	/**
	 * Background color of cell if its changeable.
	 */
	private static final Color COLOR_NOT_CHANGEABLE = new Color(240, 240, 240);

	/**
	 * Border, if cell is selected.
	 */
	private static final Border BORDER_SELECTED = BorderFactory.createLineBorder(Color.RED);

	/**
	 * Border, if cell not selected.
	 */
	private static final Border BORDER_NOT_SELECTED = BorderFactory.createLineBorder(Color.LIGHT_GRAY);

	/**
	 * Editable/not editable state of this cell.
	 */
	private boolean editable;

	/**
	 * Selected state of this cell.
	 */
	private boolean selected;

	/**
	 * Number in this cell.
	 */
	private int number;

	/**
	 * Possible numbers.
	 */
	private boolean[] possibleNumbers;

	/**
	 * Index associated with this cell panel.
	 */
	private int index;

	/**
	 * Constructor of SudokuCellPanel
	 * 
	 * @param pIndex
	 *            index associated with this cell panel
	 */
	public SudokuCellPanel(int pIndex) {
		index = pIndex;
		number = DEFAULT_NUMBER;
		setEditable(true);
		setSelected(false);
	}

	/**
	 * Allows access to the index associated with this cell panel
	 * 
	 * @return index associated with this cell panel
	 */
	public int getIndex() {
		return index;
	}

	/**
	 * 
	 * @return
	 */
	public boolean isSelected() {
		return selected;
	}

	/**
	 * 
	 * @return
	 */
	public boolean isEditable() {
		return editable;
	}

	/**
	 * Allows to set editable/not editable state of this cell.
	 * 
	 * @param pEditable
	 */
	public void setEditable(boolean pEditable) {
		editable = pEditable;
		if (pEditable) {
			setBackground(COLOR_CHANGEABLE);
		} else {
			setBackground(COLOR_NOT_CHANGEABLE);
		}
	}

	/**
	 * Clears this cell
	 */
	public void clear() {
		setLayout(new BorderLayout());
		removeAll();
		number = DEFAULT_NUMBER;
		possibleNumbers = null;
		updateUI();
	}

	/**
	 * 
	 * @param pPossibleNumbers
	 */
	public void setPossibleNumbers(boolean[] pPossibleNumbers) {
		if (pPossibleNumbers.length != 9) {
			throw new RuntimeException("Not today!");
		}

		clear();
		possibleNumbers = pPossibleNumbers;

		setLayout(new GridLayout(3, 3));

		for (int i = 0; i < pPossibleNumbers.length; i++) {
			if (pPossibleNumbers[i]) {
				add(new SudokuCellPossibleNumberLabel((i + 1) + ""));
			} else {
				add(new SudokuCellEmptyLabel());
			}
		}
	}

	/**
	 * 
	 * @return
	 */
	public boolean[] getPossibleNumbers() {
		return possibleNumbers;
	}

	/**
	 * 
	 * @param pNumber
	 */
	public void setNumber(int pNumber) {
		clear();
		number = pNumber;
		add(new SudokuCellNumberLabel(pNumber + ""));
	}

	/**
	 * Allows access to the number in this cell.
	 * 
	 * @return
	 */
	public int getNumber() {
		return number;
	}

	/**
	 * 
	 * @param pSelected
	 */
	public void setSelected(boolean pSelected) {
		selected = pSelected;
		if (pSelected) {
			setBorder(BORDER_SELECTED);
		} else {
			setBorder(BORDER_NOT_SELECTED);
			setBackground(Color.WHITE);
		}
	}
}
